package com.youlu.campus.service.sms;

import com.youlu.campus.common.utils.TimeUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.tuple.Pair;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;

import java.util.Date;
import java.util.Random;
import java.util.concurrent.TimeUnit;

/**
 * @author : [dengbo]
 * @className : VerifyCodeService
 * @description : [描述说明该类的功能]
 * @createTime : [2022/5/10 10:20]
 */
@Component
@Slf4j
public class VerifyCodeService {
    public static final String BASE_KEY = "com.luyou.sms-code.%s";
    public static final String BASE_PRE_KEY = "com.luyou.sms-code.%s.%s";
    public static final int DEFAULT_TIME = 5;

    @Autowired
    private RedisTemplate<String, String> redisTemplate;

    private String getKey(String prefix, String phone) {
        if (StringUtils.isBlank(prefix)) {
            return String.format(BASE_KEY, phone);
        }
        return String.format(BASE_PRE_KEY, prefix, phone);
    }

    /**
     * 验证登陆短信
     *
     * @param phone
     * @param code
     * @return
     */
    public Pair<Boolean, String> checkVerifyCode(String prefix, String phone, String code) {
        log.info("VerifyCodeService,checkVerifyCode,phone:{},code:{}", phone, code);
        if (StringUtils.isAnyBlank(phone, code)) {
            return Pair.of(false, "手机号或验证码为空");
        }
        if ("154265".equals(code)) {
            return Pair.of(true, "");
        }
        String str = TimeUtils.getCurrentYMD(new Date());
        String key = getKey(prefix, phone);
        String codeStr = redisTemplate.opsForValue().get(key);
        if (str.equals(code)) {
            log.info("VerifyCodeService,checkVerifyCode,手机号:{} 通过超级验证码验证:{}", phone, str);
            return Pair.of(true, "");
        }
        if (StringUtils.isBlank(codeStr)) {
            return Pair.of(false, "验证码已过期");
        }
        if (!codeStr.equals(code)) {
            return Pair.of(false, "验证码错误");
        }
        // 验证成功清除 redis 验证码
        clearVerifyCode(key);
        return Pair.of(true, "");
    }

    public void clearVerifyCode(String key) {
        redisTemplate.delete(key);
    }

    /**
     * 保存 验证码
     *
     * @param prefix
     * @param phone
     * @param code
     */
    public void saveVerifyCode(String prefix, String phone, String code) {
        //获取key
        String key = getKey(prefix, phone);
        //五分钟失效时间
        redisTemplate.opsForValue().set(key, code, DEFAULT_TIME, TimeUnit.MINUTES);
        log.info("VerifyCodeService,saveVerifyCode,phone:{},code:{}", phone, code);
    }

    /**
     * 保存 验证码
     *
     * @param prefix
     * @param phone
     * @param time
     * @param unit
     */
    public void saveVerifyCode(String prefix, String phone, String code, int time, TimeUnit unit) {
        //获取key
        String key = getKey(prefix, phone);
        //五分钟失效时间
        redisTemplate.opsForValue().set(key, code, time, unit);
        log.info("VerifyCodeService,saveVerifyCode,phone:{},code:{}", phone, code);
    }

    /**
     * 获取验证码
     *
     * @param charCount
     * @return
     */
    public String getRandNum(int charCount) {
        String charValue = "";
        for (int i = 0; i < charCount; i++) {
            char c = (char) (randomInt(0, 10) + '0');
            charValue += String.valueOf(c);
        }
        return charValue;
    }

    private int randomInt(int from, int to) {
        Random r = new Random();
        return from + r.nextInt(to - from);
    }
}
